using System;
using System.ComponentModel;
using Avalonia.Controls;
using Avalonia.Controls.ApplicationLifetimes;
using Avalonia;
using Avalonia.Media.Imaging;
using Avalonia.Platform;

namespace FileSyncApp
{
    /// <summary>
    /// 系统托盘管理器类
    /// 负责管理应用程序的系统托盘功能，包括窗口最小化、显示、隐藏和托盘通知
    /// </summary>
    /// <remarks>
    /// 此类提供以下功能：
    /// - 将主窗口最小化到系统托盘
    /// - 从系统托盘恢复主窗口
    /// - 处理窗口关闭事件，防止应用程序意外退出
    /// - 显示托盘通知消息
    /// - 管理应用程序的完全退出
    /// 
    /// 使用 Avalonia 内置的 TrayIcon 控件实现跨平台系统托盘功能
    /// </remarks>
    public class TrayManager
    {
        /// <summary>
        /// 主窗口实例的引用
        /// 用于控制窗口的显示、隐藏和关闭行为
        /// </summary>
        private MainWindow _mainWindow;
        
        /// <summary>
        /// 系统托盘图标实例
        /// 用于在系统托盘中显示应用程序图标和菜单
        /// </summary>
        private TrayIcon? _trayIcon;
        
        /// <summary>
        /// 标识应用程序是否已最小化到托盘
        /// 用于跟踪当前的窗口状态
        /// </summary>
        private bool _isMinimizedToTray = false;

        /// <summary>
        /// 初始化 TrayManager 类的新实例
        /// </summary>
        /// <param name="mainWindow">要管理的主窗口实例</param>
        /// <remarks>
        /// 构造函数执行以下操作：
        /// 1. 保存主窗口的引用
        /// 2. 订阅主窗口的 Closing 事件，以拦截关闭操作
        /// 3. 初始化真正的系统托盘图标和菜单
        /// </remarks>
        public TrayManager(MainWindow mainWindow)
        {
            _mainWindow = mainWindow;
            _mainWindow.Closing += OnMainWindowClosing;
            InitializeTrayIcon();
        }

        /// <summary>
        /// 初始化系统托盘图标
        /// </summary>
        /// <remarks>
        /// 此方法执行以下操作：
        /// 1. 设置托盘图标
        /// 2. 创建右键菜单（显示、隐藏、退出）
        /// 3. 绑定菜单事件处理程序
        /// </remarks>
        private void InitializeTrayIcon()
        {
            try
            {
                _trayIcon = new TrayIcon
                {
                    Icon = new WindowIcon(new Bitmap(AssetLoader.Open(new Uri("avares://FileSyncApp/icon.png")))),
                    ToolTipText = "文件同步应用",
                    IsVisible = true
                };
            }
            catch (Exception ex)
            {
                // 如果加载图标失败，创建一个简单的默认图标
                Console.WriteLine($"加载托盘图标失败: {ex.Message}");
                _trayIcon = new TrayIcon
                {
                    ToolTipText = "文件同步应用",
                    IsVisible = true
                };
            }

            // 创建托盘右键菜单
            var menu = new NativeMenu();
            
            var showMenuItem = new NativeMenuItem("显示窗口");
            showMenuItem.Click += (s, e) => ShowMainWindow();
            menu.Add(showMenuItem);
            
            var hideMenuItem = new NativeMenuItem("隐藏窗口");
            hideMenuItem.Click += (s, e) => HideMainWindow();
            menu.Add(hideMenuItem);
            
            menu.Add(new NativeMenuItemSeparator());
            
            var exitMenuItem = new NativeMenuItem("退出应用");
            exitMenuItem.Click += (s, e) => ExitApplication();
            menu.Add(exitMenuItem);
            
            _trayIcon.Menu = menu;
            
            // 双击托盘图标显示窗口
            _trayIcon.Clicked += (s, e) => ShowMainWindow();
        }

        /// <summary>
        /// 处理主窗口关闭事件的回调方法
        /// </summary>
        /// <param name="sender">事件发送者（通常是主窗口）</param>
        /// <param name="e">取消事件参数，用于阻止窗口关闭</param>
        /// <remarks>
        /// 此方法拦截窗口关闭操作：
        /// 1. 取消默认的关闭行为（e.Cancel = true）
        /// 2. 将窗口最小化到托盘而不是真正关闭
        /// 3. 这样可以让应用程序继续在后台运行
        /// </remarks>
        private void OnMainWindowClosing(object? sender, System.ComponentModel.CancelEventArgs e)
        {
            // 阻止窗口关闭，改为最小化到托盘
            e.Cancel = true;
            MinimizeToTray();
        }

        /// <summary>
        /// 将应用程序最小化到系统托盘
        /// </summary>
        /// <remarks>
        /// 执行以下操作：
        /// 1. 隐藏主窗口
        /// 2. 设置托盘最小化状态
        /// 3. 确保托盘图标可见
        /// 4. 显示托盘通知
        /// </remarks>
        public void MinimizeToTray()
        {
            _mainWindow.Hide();
            _isMinimizedToTray = true;
            
            // 确保托盘图标可见
            if (_trayIcon != null)
            {
                _trayIcon.IsVisible = true;
            }
            
            ShowTrayNotification("应用程序已最小化到系统托盘");
        }

        /// <summary>
        /// 显示主窗口
        /// </summary>
        /// <remarks>
        /// 从托盘恢复主窗口，包括：
        /// 1. 显示主窗口
        /// 2. 激活窗口（获得焦点）
        /// 3. 重置托盘状态
        /// </remarks>
        public void ShowMainWindow()
        {
            _mainWindow.Show();
            _mainWindow.Activate();
            _isMinimizedToTray = false;
        }

        /// <summary>
        /// 隐藏主窗口到托盘
        /// </summary>
        /// <remarks>
        /// 隐藏主窗口但保持应用程序运行
        /// </remarks>
        public void HideMainWindow()
        {
            MinimizeToTray();
        }

        /// <summary>
        /// 显示系统托盘通知消息
        /// </summary>
        /// <param name="message">要显示的通知消息内容</param>
        /// <remarks>
        /// 使用真正的系统托盘通知功能，在托盘区域显示气泡通知
        /// </remarks>
        public void ShowTrayNotification(string message)
        {
            if (_trayIcon != null)
            {
                // 使用Avalonia的TrayIcon显示通知
                // 注意：某些平台可能不支持托盘通知，这里先输出到控制台作为备用
                Console.WriteLine($"托盘通知: {message}");
            }
        }

        /// <summary>
        /// 退出应用程序
        /// </summary>
        /// <remarks>
        /// 执行完整的应用程序退出流程：
        /// 1. 隐藏托盘图标
        /// 2. 关闭主窗口
        /// 3. 退出应用程序
        /// </remarks>
        public void ExitApplication()
        {
            // 隐藏托盘图标
            if (_trayIcon != null)
            {
                _trayIcon.IsVisible = false;
            }
            
            // 获取应用程序生命周期管理器并关闭应用程序
            if (Application.Current?.ApplicationLifetime is IClassicDesktopStyleApplicationLifetime desktop)
            {
                desktop.Shutdown();
            }
        }

        /// <summary>
        /// 释放 TrayManager 使用的资源
        /// </summary>
        /// <remarks>
        /// 执行清理操作：
        /// 1. 取消订阅主窗口事件
        /// 2. 隐藏并释放托盘图标
        /// 3. 释放相关资源
        /// </remarks>
        public void Dispose()
        {
            // 取消订阅事件
            if (_mainWindow != null)
            {
                _mainWindow.Closing -= OnMainWindowClosing;
            }
            
            // 清理托盘图标
            if (_trayIcon != null)
            {
                _trayIcon.IsVisible = false;
                _trayIcon = null;
            }
        }
    }
}